
<!DOCTYPE html>
<html lang="en">
    <head><meta name="generator" content="Hexo 3.9.0">
    
        <title>FairyGUI - 插入模型/粒子/Spine/Canvas</title>
    
        <meta charset="utf-8">
        <meta name="description" content="FairyGUI教程">
        <meta name="keywords" content="FairyGUI,FGUI,FairyGUI教程">
        
        <meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1, user-scalable=no">

        <meta property="og:type" content="article">
        <meta property="og:title" content="-插入模型/粒子/Spine/CanvasFairyGUI">
        <meta property="og:description" content="FairyGUI教程">

        <meta name="twitter:card" content="summary">
        <meta name="twitter:title" content="插入模型/粒子/Spine/Canvas — FairyGUI">
        <meta name="twitter:description" content="FairyGUI教程">

      <!--  <link href='//fonts.proxy.ustclug.org/css?family=Source+Sans+Pro:300,400,600|Roboto Mono' rel='stylesheet' type='text/css'> -->

        <!-- main page styles -->
        <link rel="stylesheet" href="/docs/css/page.css">

        <!-- this needs to be loaded before guide's inline scripts -->
        <script src="/docs/js/vue.min.js"></script>
        <script>window.PAGE_TYPE = "guide_unity"</script>
    </head>
    <body class="docs">        <div id="mobile-bar" data-bg-text="FairyGUI">
            <a class="menu-button"></a>
        </div>
        <div id="header">
  <ul id="nav">
    <li><a href="/docs/guide/" class="nav-link current">教程</a></li>
<li><a href="/docs/examples/" class="nav-link">在线示例</a></li>
<li><a href="/docs/release_notes/" class="nav-link">发行日志</a></li>
<li><a href="/" class="nav-link">首页</a></li>
  </ul>
</div>

        
            <div id="main" class="fix-sidebar">
                
                    
    <div class="sidebar">
    <ul class="main-menu">
        <li><a href="/docs/guide/" class="nav-link current">教程</a></li>
<li><a href="/docs/examples/" class="nav-link">在线示例</a></li>
<li><a href="/docs/release_notes/" class="nav-link">发行日志</a></li>
<li><a href="/" class="nav-link">首页</a></li>
    </ul>
    <div class="list">
        <ul class="menu-root">
            

	 			
	                
	                <li>
	                    <a href="/docs/guide/index.html" class="sidebar-link">导读</a>
	                </li>
	            
	
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/index.html" class="sidebar-link">编辑器使用基础</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/project_settings.html" class="sidebar-link">项目设置</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/package.html" class="sidebar-link">包</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/branch.html" class="sidebar-link">分支</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/publish.html" class="sidebar-link">发布</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/object.html" class="sidebar-link">元件</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/image.html" class="sidebar-link">图片</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/movieclip.html" class="sidebar-link">动画</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/graph.html" class="sidebar-link">图形</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/loader.html" class="sidebar-link">装载器</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/text.html" class="sidebar-link">文本</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/richtext.html" class="sidebar-link">富文本</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/group.html" class="sidebar-link">组</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/component.html" class="sidebar-link">组件</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/scrollpane.html" class="sidebar-link">滚动容器</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/controller.html" class="sidebar-link">控制器</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/relation.html" class="sidebar-link">关联系统</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/label.html" class="sidebar-link">标签</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/button.html" class="sidebar-link">按钮</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/combobox.html" class="sidebar-link">下拉框</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/progressbar.html" class="sidebar-link">进度条</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/slider.html" class="sidebar-link">滑动条</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/scrollbar.html" class="sidebar-link">滚动条</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/list.html" class="sidebar-link">列表</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/tree.html" class="sidebar-link">树</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/popup.html" class="sidebar-link">Popup</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/dragdrop.html" class="sidebar-link">Drag&Drop</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/window.html" class="sidebar-link">窗口系统</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/transition.html" class="sidebar-link">动效</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/adaptation.html" class="sidebar-link">适配</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/i18n.html" class="sidebar-link">多国语言</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/export.html" class="sidebar-link">导入和导出</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/preference.html" class="sidebar-link">偏好设置</a>
	                </li>
	            
	                
	                <li>
	                    <a href="/docs/guide/editor/plugin.html" class="sidebar-link">插件</a>
	                </li>
	            
	
	            
	                
	                
	                <li><h3>SDK</h3></li>
	                
	                <li>
	                    <a href="/docs/guide/sdk/laya.html" class="sidebar-link">LayaAir</a>
	                </li>
	            
	                
	                
	                <li>
	                    <a href="/docs/guide/sdk/egret.html" class="sidebar-link">Egret</a>
	                </li>
	            
	                
	                
	                <li>
	                    <a href="/docs/guide/sdk/cocos2dx.html" class="sidebar-link">Cocos2dx</a>
	                </li>
	            
	                
	                
	                <li>
	                    <a href="/docs/guide/sdk/creator.html" class="sidebar-link">Cocos Creator</a>
	                </li>
	            
	                
	                
	                <li>
	                    <a href="/docs/guide/sdk/cryengine.html" class="sidebar-link">Cry Engine</a>
	                </li>
	            

	            
	                
	                
	                <li><h3>SDK - Unity</h3></li>
	                
	                <li>
	                    <a href="/docs/guide/unity/index.html" class="sidebar-link">显示UI面板</a>
	                </li>
	            
	                
	                
	                <li>
	                    <a href="/docs/guide/unity/transform.html" class="sidebar-link">坐标系统</a>
	                </li>
	            
	                
	                
	                <li>
	                    <a href="/docs/guide/unity/atlas.html" class="sidebar-link">纹理集的处理</a>
	                </li>
	            
	                
	                
	                <li>
	                    <a href="/docs/guide/unity/font.html" class="sidebar-link">字体的处理</a>
	                </li>
	            
	                
	                
	                <li>
	                    <a href="/docs/guide/unity/input.html" class="sidebar-link">输入处理</a>
	                </li>
	            
	                
	                
	                <li>
	                    <a href="/docs/guide/unity/event.html" class="sidebar-link">事件机制</a>
	                </li>
	            
	                
	                
	                <li>
	                    <a href="/docs/guide/unity/insert3d.html" class="sidebar-link current">插入模型/粒子/Spine/Canvas</a>
	                </li>
	            
	                
	                
	                <li>
	                    <a href="/docs/guide/unity/uipainter.html" class="sidebar-link">曲面UI</a>
	                </li>
	            
	                
	                
	                <li>
	                    <a href="/docs/guide/unity/drawcall.html" class="sidebar-link">DrawCall优化</a>
	                </li>
	            
	                
	                
	                <li>
	                    <a href="/docs/guide/unity/lua.html" class="sidebar-link">在Lua中使用</a>
	                </li>
	            
	                
	                
	                <li>
	                    <a href="/docs/guide/unity/special.html" class="sidebar-link">特色功能</a>
	                </li>
	            
	                
	                
	                <li>
	                    <a href="/docs/guide/unity/faq.html" class="sidebar-link">常见问题</a>
	                </li>
	            

            
        </ul>
    </div>
</div>


<div class="content guide_unity with-sidebar ">
    
      <h1>插入模型/粒子/Spine/Canvas</h1>
    
    <p>FairyGUI提供了非常完整的解决方案解决模型、粒子、骨骼动画等3D对象与UI穿插的问题，并且支持与UGUI Canvas穿插。</p>
<h2 id="直接放入3D对象"><a href="#直接放入3D对象" class="headerlink" title="直接放入3D对象"></a>直接放入3D对象</h2><p>这种方式是直接用UI相机渲染3D对象，相比RenderTexture的方案，使用简单且节省内存，缺点是在UI相机下3D对象没有透视。</p>
<p>在UI中插入3D对象需要用到一个图形占位和<code>GoWrapper</code>对象。</p>
<ol>
<li><p>实例化你的3D对象，例如:</p>
<figure class="highlight csharp"><table><tr><td class="code"><pre><span class="line">Object prefab = Resources.Load(<span class="string">"Role/npc"</span>);</span><br><span class="line">GameObject go = (GameObject)Object.Instantiate(prefab);</span><br></pre></td></tr></table></figure>
</li>
<li><p>给3D对象设置合适的位置、缩放和旋转。</p>
<figure class="highlight csharp"><table><tr><td class="code"><pre><span class="line">go.transform.localPosition = <span class="keyword">new</span> Vector3(<span class="number">61</span>, <span class="number">-89</span>, <span class="number">1000</span>); </span><br><span class="line">go.transform.localScale = <span class="keyword">new</span> Vector3(<span class="number">180</span>, <span class="number">180</span>, <span class="number">180</span>);</span><br><span class="line">go.transform.localEulerAngles = <span class="keyword">new</span> Vector3(<span class="number">0</span>, <span class="number">100</span>, <span class="number">0</span>);</span><br></pre></td></tr></table></figure>
<p>注意：对于模型这种有“厚度”的对象（在z轴有一定范围），localPosition的z值不应该为0，可以设置一个较大的正数值（正数表示远离摄像机）。因为Shader是开启了ZTest的，如果模型在z轴的坐标为0，和UI的z值相同，那么他的前端就可能与他上一层的UI重叠。</p>
<p>模型的缩放可以根据这个公式估算：缩放倍数 = 显示大小（单位像素）/ 模型大小（单位米）。例如如果一个模型是1米高，最终需要显示400像素高，那么需要放大400倍。</p>
</li>
<li><p>在UI中放置一个空白的图形，假设名称为“holder”。</p>
<figure class="highlight csharp"><table><tr><td class="code"><pre><span class="line">GGraph holder = view.GetChild(<span class="string">"holder"</span>).asGraph;</span><br></pre></td></tr></table></figure>
</li>
<li><p>构建GoWrapper对象，放入到holder中。</p>
<figure class="highlight csharp"><table><tr><td class="code"><pre><span class="line">GoWrapper wrapper = <span class="keyword">new</span> GoWrapper(go);</span><br><span class="line">holder.SetNativeObject(wrapper);</span><br></pre></td></tr></table></figure>
</li>
</ol>
<p><strong>点击处理</strong></p>
<p>GoWrapper默认是没有大小的，所以不能处理点击事件。如果需要对3D对象显示区域的点击事件，可以在holder上再放置一个图形（透明度设置为0）作为点击区域，或者一个空组件也行。</p>
<p><strong>调试方式</strong></p>
<p>使用这种方式插入3D对象，需要使用代码，并在运行时才能看到效果，对设置GameObject的位置、旋转、缩放等都不太直观。FairyGUI提供了直观的方法，可以把3D对象直接挂到UIPanel对象下。<strong>首先设置3D对象的Layer为UI</strong>，然后勾选UIPanel的“Set Native Children Order”。如下：</p>
<p><img src="../../images/20170809140223.png" alt></p>
<p>但这种方法GameObject并不会随着UIPanel的移动而移动，因此只能用作调试用途。例如制作UI上用的粒子时，可以提供这种方法给美术。</p>
<p><strong>更新GameObject</strong></p>
<p>GoWrapper会在构造函数里查询你的GameObject里所有的Renderer并保存。如果你的GameObject后续发生了改变，需要告知GoWrapper重新查询和保存，否则显示不正确。</p>
<figure class="highlight csharp"><table><tr><td class="code"><pre><span class="line">wrapper.CacheRenderers();</span><br></pre></td></tr></table></figure>
<p><strong>更换GameObject</strong></p>
<p>如果要修改GoWrapper包装的对象，可以使用：</p>
<figure class="highlight csharp"><table><tr><td class="code"><pre><span class="line">wrapper.wrapTarget = anotherGameObject;</span><br></pre></td></tr></table></figure>
<p>设置新的包装对象后，原来的包装对象只会被删除引用，但不会被销毁。如果你要销毁原来的GameObject，必须自行处理，例如：</p>
<figure class="highlight csharp"><table><tr><td class="code"><pre><span class="line">Object.Destroy(wrapper.wrapTarget);</span><br><span class="line">wrapper.wrapTarget = anotherGameObject;</span><br></pre></td></tr></table></figure>
<p><strong>复制材质</strong></p>
<p>如果GoWrapper包装的对象是在很多地方同时使用，而且你在实例化时没有自行处理材质的复制，那么会产生一些问题。例如一个模型，你既在UI上显示，也在场景中使用，UI系统需要修改模型的材质参数，这就会对场景中的显示产生影响。造成这个问题的根源是GoWrapper默认是使用共享材质的，这是出于效率的影响。要解决这个问题，有两种途径。一、在你实例化对象时自行复制材质。你需要小心处理，避免过度的复制操作。二、让GoWrapper自动复制。在设置包装对象时这样调用即可：</p>
<figure class="highlight csharp"><table><tr><td class="code"><pre><span class="line"><span class="comment">//第二个参数为true，表示复制材质</span></span><br><span class="line">wrapper.setWrapTarget(anotherGameObject, <span class="literal">true</span>);</span><br></pre></td></tr></table></figure>
<p><strong>剪裁</strong></p>
<p>如果需要对3D对象进行剪裁，可以利用自定义遮罩（<strong>模型、粒子、骨骼动画等均适用</strong>）。自定义遮罩的使用方法参考：<a href="../editor/component.html#遮罩">组件的遮罩</a>。</p>
<p>例如需要在一个列表内的item显示模型，并希望模型在列表滚动时被正确隐藏，这时仅通过列表自身的溢出滚动功能是无法实现的。首先将列表转换为一个组件，在组件内拖入一个矩形图形覆盖列表的视口，然后将这个图形设置为组件的自定义遮罩。</p>
<p>模型的着色器也必须做出相应的修改，把以下代码添加到模型的着色器的Properties段（可参考FairyGUI-Image.shader）：</p>
<figure class="highlight csharp"><table><tr><td class="code"><pre><span class="line">_StencilComp (<span class="string">"Stencil Comparison"</span>, Float) = <span class="number">8</span></span><br><span class="line">_Stencil (<span class="string">"Stencil ID"</span>, Float) = <span class="number">0</span></span><br><span class="line">_StencilOp (<span class="string">"Stencil Operation"</span>, Float) = <span class="number">0</span></span><br><span class="line">_StencilWriteMask (<span class="string">"Stencil Write Mask"</span>, Float) = <span class="number">255</span></span><br><span class="line">_StencilReadMask (<span class="string">"Stencil Read Mask"</span>, Float) = <span class="number">255</span></span><br></pre></td></tr></table></figure>
<p>把以下代码加到模型的着色器的SubShader段（可参考FairyGUI-Image.shader）：</p>
<figure class="highlight csharp"><table><tr><td class="code"><pre><span class="line">Stencil</span><br><span class="line">&#123;</span><br><span class="line">    Ref [_Stencil]</span><br><span class="line">    Comp [_StencilComp]</span><br><span class="line">    Pass [_StencilOp] </span><br><span class="line">    ReadMask [_StencilReadMask]</span><br><span class="line">    WriteMask [_StencilWriteMask]</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>
<p>最后，设置GoWrapper支持自定义遮罩：</p>
<figure class="highlight csharp"><table><tr><td class="code"><pre><span class="line">wrapper.supportStencil = <span class="literal">true</span>;</span><br></pre></td></tr></table></figure>
<p><strong>注意，如果有多个相同的被剪裁的对象，他们的材质不能共用一个，否则会出现显示异常。解决方法是复制材质，请参考上一段，复制材质。</strong></p>
<h2 id="使用RenderTexture"><a href="#使用RenderTexture" class="headerlink" title="使用RenderTexture"></a>使用RenderTexture</h2><p>在UI上展现3D内容的另一种方式是使用RenderTexture。使用RenderTexture的步骤比较复杂，需要另外新建相机渲染目标对象，然后把该相机的输出定向到一张RenderTexture。有了RenderTexture后，我们将它赋值到Image.texture即可。详细的代码可以参考<a href="https://github.com/fairygui/FairyGUI-unity/blob/master/Assets/Examples/RenderTexture/RenderImage.cs" target="_blank" rel="noopener">RenderImage</a>。</p>
<p>RenderTexture可以设置背景颜色为透明，方便和UI混合，具体在例子中就是把“this._image.blendMode = BlendMode.Off;”注释掉即可。但如果渲染的内容包含有透明贴图，那么和UI混合时就会出现透明部分的显示错误，有两种解决方案，第一种方案可以参考<a href="https://blog.uwa4d.com/archives/Severe_MOBA.html" target="_blank" rel="noopener">这里的资料</a>，修改模型或者粒子的着色器，以及RenderTexture的着色器。 第二种方案是FairyGUI提供的独特方案，也就是像RenderImage演示的那样，将RenderTexture所在位置的背景图片影射到RenderTexture渲染相机的背景上：</p>
<figure class="highlight csharp"><table><tr><td class="code"><pre><span class="line"><span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">SetBackground</span>(<span class="params">GObject image</span>)</span>;</span><br><span class="line"><span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">SetBackground</span>(<span class="params">GObject image1, GObject image2</span>)</span>;</span><br></pre></td></tr></table></figure>
<p>可以看到，最多可以设置两个图片。如果RenderTexture的背后有超过两个图片的叠加，就无法处理了。这两个图片不需要和RenderTexture在同一个容器里，它们可以在UI的任何层次。</p>
<h2 id="插入Canvas"><a href="#插入Canvas" class="headerlink" title="插入Canvas"></a>插入Canvas</h2><p>FairyGUI无论从功能上还是效率上，都能满足所有大部分UI设计的需求，因此在使用FairyGUI的项目里，很少会有需要再使用UGUI的情况。大部分UGUI需要用插件完成的功能，FairyGUI均已经内置，而且很多可以在编辑器零脚本完成。如果确实需要用到一些UGUI的插件，并且不方便移植，FairyGUI也提供了方案插入UGUI的Canvas到FairyGUI的显示层次中。步骤如下：</p>
<ol>
<li>设置Canvas的Render Mode为WorldSpace，Event Camera为Stage Camera。</li>
<li>删除Canvas Scaler组件（如果有）。</li>
<li><p>使用GoWrapper包装Canvas：</p>
<figure class="highlight csharp"><table><tr><td class="code"><pre><span class="line">GameObject canvasObject;</span><br><span class="line">GoWrapper gw = <span class="keyword">new</span> GoWrapper(canvasObject);</span><br></pre></td></tr></table></figure></li>
</ol>

    
    <div class="footer">
      发现错误或想贡献文档?
      <a href="https://github.com/fairygui/fairygui.github.io/tree/master/src/guide/unity/insert3d.md" target="_blank">
        在 Github 上编辑此文档!
      </a>
    </div>
</div>

                
            </div>
            <script src="/docs/js/smooth-scroll.min.js"></script>
        

        <!-- main custom script for sidebars, version selects etc. -->        
        <script src="/docs/js/css.escape.js"></script>
        <script src="/docs/js/common.js"></script>
    </body>
</html>
